<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width, initial-scale=1, maximum-scale=1">
    <meta name="keywords" content="Hexo Theme Keep">
    <meta name="description" content="Hexo Theme Keep">
    <meta name="author" content="aaton">
    
    <title>
        
            ES6之解构 |
        
        aaton&#39;s study notes
    </title>
    
<link rel="stylesheet" href="/css/style.css">

    <link rel="shortcut icon" href="/images/logo.svg">
    
<link rel="stylesheet" href="/font/css/fontawesome.min.css">

    
<link rel="stylesheet" href="/font/css/regular.min.css">

    
<link rel="stylesheet" href="/font/css/solid.min.css">

    
<link rel="stylesheet" href="/font/css/brands.min.css">

    <script id="hexo-configurations">
    let KEEP = window.KEEP || {}
    KEEP.hexo_config = {"hostname":"example.com","root":"/","language":"en"}
    KEEP.theme_config = {"toc":{"enable":false,"number":false,"expand_all":false,"init_open":false},"style":{"primary_color":"#0066cc","logo":"/images/logo.svg","favicon":"/images/logo.svg","avatar":"/images/avatar.svg","font_size":null,"font_family":null,"hover":{"shadow":false,"scale":false},"first_screen":{"enable":true,"header_transparent":true,"background_img":"/images/bg.svg","description":"Keep writing and Keep loving.","font_color":null,"hitokoto":true},"scroll":{"progress_bar":false,"percent":false}},"local_search":{"enable":false,"preload":false},"code_copy":{},"code_block":{"tools":{"enable":true,"style":"default"},"highlight_theme":"default"},"side_tools":{},"pjax":{"enable":false},"lazyload":{"enable":false},"comment":{"enable":false,"use":"valine","valine":{"appid":null,"appkey":null,"server_urls":null,"placeholder":null},"gitalk":{"github_id":null,"github_admins":null,"repository":null,"client_id":null,"client_secret":null,"proxy":null},"twikoo":{"env_id":null,"region":null,"version":"1.6.8"},"waline":{"server_url":null,"reaction":false,"version":2}},"post":{"author_label":{"enable":true,"auto":true,"custom_label_list":["Trainee","Engineer","Architect"]},"word_count":{"enable":true,"wordcount":true,"min2read":true},"img_align":"left","copyright_info":false},"version":"3.6.1"}
    KEEP.language_ago = {"second":"%s seconds ago","minute":"%s minutes ago","hour":"%s hours ago","day":"%s days ago","week":"%s weeks ago","month":"%s months ago","year":"%s years ago"}
    KEEP.language_code_block = {"copy":"Copy code","copied":"Copied","fold":"Fold code block","folded":"Folded"}
    KEEP.language_copy_copyright = {"copy":"Copy copyright info","copied":"Copied","title":"Original article title","author":"Original article author","link":"Original article link"}
  </script>
<meta name="generator" content="Hexo 6.3.0"></head>


<body>
<div class="progress-bar-container">
    

    
</div>


<main class="page-container">

    

    <div class="page-main-content">

        <div class="page-main-content-top">
            
<header class="header-wrapper">

    <div class="header-content">
        <div class="left">
            
                <a class="logo-image" href="/">
                    <img src="/images/logo.svg">
                </a>
            
            <a class="logo-title" href="/">
               aaton&#39;s study notes
            </a>
        </div>

        <div class="right">
            <div class="pc">
                <ul class="menu-list">
                    
                        <li class="menu-item">
                            <a class=""
                               href="/"
                            >
                                HOME
                            </a>
                        </li>
                    
                        <li class="menu-item">
                            <a class=""
                               href="/archives"
                            >
                                ARCHIVES
                            </a>
                        </li>
                    
                        <li class="menu-item">
                            <a class=""
                               href="/tags"
                            >
                                TAGS
                            </a>
                        </li>
                    
                        <li class="menu-item">
                            <a class=""
                               href="/categories"
                            >
                                CATEGORIES
                            </a>
                        </li>
                    
                        <li class="menu-item">
                            <a class=""
                               href="/about"
                            >
                                ABOUT
                            </a>
                        </li>
                    
                    
                </ul>
            </div>
            <div class="mobile">
                
                <div class="icon-item menu-bar">
                    <div class="menu-bar-middle"></div>
                </div>
            </div>
        </div>
    </div>

    <div class="header-drawer">
        <ul class="drawer-menu-list">
            
                <li class="drawer-menu-item flex-center">
                    <a class=""
                       href="/">HOME</a>
                </li>
            
                <li class="drawer-menu-item flex-center">
                    <a class=""
                       href="/archives">ARCHIVES</a>
                </li>
            
                <li class="drawer-menu-item flex-center">
                    <a class=""
                       href="/tags">TAGS</a>
                </li>
            
                <li class="drawer-menu-item flex-center">
                    <a class=""
                       href="/categories">CATEGORIES</a>
                </li>
            
                <li class="drawer-menu-item flex-center">
                    <a class=""
                       href="/about">ABOUT</a>
                </li>
            
        </ul>
    </div>

    <div class="window-mask"></div>

</header>


        </div>

        <div class="page-main-content-middle">

            <div class="main-content">

                
                    <div class="fade-in-down-animation">
    <div class="post-page-container">
        <div class="article-content-container">

            <div class="article-title">
                <span class="title-hover-animation">ES6之解构</span>
            </div>

            
                <div class="article-header">
                    <div class="avatar">
                        <img src="/images/avatar.svg">
                    </div>
                    <div class="info">
                        <div class="author">
                            <span class="name">aaton</span>
                            
                                <span class="author-label">Lv3</span>
                            
                        </div>
                        <div class="meta-info">
                            
<div class="article-meta-info">
    <span class="article-date article-meta-item">
        
            <i class="fa-regular fa-calendar-plus"></i>&nbsp;
        
        <span class="pc">2023-06-05 16:00:53</span>
        <span class="mobile">2023-06-05 16:00</span>
    </span>
    
        <span class="article-update-date article-meta-item">
        <i class="fas fa-file-pen"></i>&nbsp;
        <span class="pc">2023-12-06 16:45:42</span>
    </span>
    
    
        <span class="article-categories article-meta-item">
            <i class="fas fa-folder"></i>&nbsp;
            <ul>
                
                    <li>
                        <a href="/categories/Javascript/">Javascript</a>&nbsp;
                    </li>
                
            </ul>
        </span>
    
    
        <span class="article-tags article-meta-item">
            <i class="fas fa-tags"></i>&nbsp;
            <ul>
                
                    <li>
                        <a href="/tags/%E8%A7%A3%E6%9E%84/">解构</a>&nbsp;
                    </li>
                
                    <li>
                        | <a href="/tags/ES6/">ES6</a>&nbsp;
                    </li>
                
            </ul>
        </span>
    

    
    
        <span class="article-wordcount article-meta-item">
            <i class="fas fa-file-word"></i>&nbsp;<span>4.5k Words</span>
        </span>
    
    
        <span class="article-min2read article-meta-item">
            <i class="fas fa-clock"></i>&nbsp;<span>18 Mins</span>
        </span>
    
    
        <span class="article-pv article-meta-item">
            <i class="fas fa-eye"></i>&nbsp;<span id="busuanzi_value_page_pv"></span>
        </span>
    
</div>

                        </div>
                    </div>
                </div>
            

            <div class="article-content keep-markdown-body">
                

                <p><img src="https://cn.bing.com/th?id=OHR.MauiBeach_ZH-CN1435658101_1920x1080.webp&qlt=50" alt="bing.com-怀阿纳帕纳帕州立公园的黑沙滩，茂宜岛，夏威夷，美国" title="bing.com-怀阿纳帕纳帕州立公园的黑沙滩，茂宜岛，夏威夷，美国"></p>
<p>解构赋值允许你使用类似数组或对象字面量的语法将数组和对象的属性赋给各种变量。这种赋值语法极度简洁，同时还比传统的属性访问方法更为清晰。</p>
<span id="more"></span>

<h1 id="1、数组的解构赋值"><a href="#1、数组的解构赋值" class="headerlink" title="1、数组的解构赋值"></a>1、数组的解构赋值</h1><h3 id="基本用法"><a href="#基本用法" class="headerlink" title="基本用法"></a>基本用法</h3><p>以前，为变量赋值，只能直接指定值。</p>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line">let a = 1;</span><br><span class="line">let b = 2;</span><br><span class="line">let c = 3;</span><br></pre></td></tr></table></figure>
<p>但是在ES6中允许写成这样：</p>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">let [a,b,c] = [1,2,3];</span><br></pre></td></tr></table></figure>

<p>上面代码表示，可以<strong>从数组中提取值，按照对应位置，对变量赋值</strong>。</p>
<p>本质上，这种写法属于“模式匹配”，<strong>只要等号两边的模式相同，左边的变量就会被赋予对应的值</strong>。下面是一些使用嵌套数组进行解构的例子。</p>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br></pre></td><td class="code"><pre><span class="line">let [foo, [[bar], baz]] = [1, [[2], 3]];</span><br><span class="line">foo // 1</span><br><span class="line">bar // 2</span><br><span class="line">baz // 3</span><br><span class="line">let [ , , third] = [&quot;foo&quot;, &quot;bar&quot;, &quot;baz&quot;];</span><br><span class="line">third // &quot;baz&quot;</span><br><span class="line">let [x, , y] = [1, 2, 3];</span><br><span class="line">x // 1</span><br><span class="line">y // 3</span><br><span class="line">let [head, ...tail] = [1, 2, 3, 4];</span><br><span class="line">head // 1</span><br><span class="line">tail // [2, 3, 4]</span><br><span class="line">let [x, y, ...z] = [&#x27;a&#x27;];</span><br><span class="line">x // &quot;a&quot;</span><br><span class="line">y // undefined</span><br><span class="line">z // []</span><br></pre></td></tr></table></figure>
<p>如果<strong>解构不成功，变量的值就等于undefined</strong>。</p>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line">let [foo] = [];</span><br><span class="line">let [bar, foo] = [1];</span><br></pre></td></tr></table></figure>
<p>以上两种情况都属于解构不成功，foo的值都会等于undefined。</p>
<p>另一种情况是<strong>不完全解构，即等号左边的模式，只匹配一部分的等号右边的数组</strong>。这种情况下，解构依然<strong>可以成功</strong>。</p>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br></pre></td><td class="code"><pre><span class="line">let [x, y] = [1, 2, 3];</span><br><span class="line">x // 1</span><br><span class="line">y // 2</span><br><span class="line">let [a, [b], d] = [1, [2, 3], 4];</span><br><span class="line">a // 1</span><br><span class="line">b // 2</span><br><span class="line">d // 4</span><br></pre></td></tr></table></figure>
<p>上面两个例子，都属于不完全解构，但是可以成功。</p>
<p>如果等号的右边不是数组（或者严格地说，不是可遍历的结构，参见<a class="link"   target="_blank" rel="noopener" href="https://www.bookstack.cn/read/es6-3rd/docs-iterator.md" >《Iterator》<i class="fas fa-external-link-alt"></i></a>一章），那么将会报错。</p>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br></pre></td><td class="code"><pre><span class="line">// 报错</span><br><span class="line">let [foo] = 1;</span><br><span class="line">let [foo] = false;</span><br><span class="line">let [foo] = NaN;</span><br><span class="line">let [foo] = undefined;</span><br><span class="line">let [foo] = null;</span><br><span class="line">let [foo] = &#123;&#125;;</span><br></pre></td></tr></table></figure>
<p>上面的语句都会报错，因为等号右边的值，要么转为对象以后不具备 Iterator 接口（前五个表达式），要么本身就不具备 Iterator 接口（最后一个表达式）。</p>
<p>对于 Set 结构，也可以使用数组的解构赋值。</p>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line">let [x, y, z] = new Set([&#x27;a&#x27;, &#x27;b&#x27;, &#x27;c&#x27;]);</span><br><span class="line">x // &quot;a&quot;</span><br></pre></td></tr></table></figure>

<p>事实上，<strong>只要某种数据结构具有 Iterator 接口，都可以采用数组形式的解构赋值</strong>。</p>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br></pre></td><td class="code"><pre><span class="line">function* fibs() &#123;</span><br><span class="line">  let a = 0;</span><br><span class="line">  let b = 1;</span><br><span class="line">  while (true) &#123;</span><br><span class="line">    yield a;</span><br><span class="line">    [a, b] = [b, a + b];</span><br><span class="line">  &#125;</span><br><span class="line">&#125;</span><br><span class="line">let [first, second, third, fourth, fifth, sixth] = fibs();</span><br><span class="line">sixth // 5</span><br></pre></td></tr></table></figure>
<p>上面代码中，fibs是一个 Generator 函数（参见<a class="link"   target="_blank" rel="noopener" href="https://www.bookstack.cn/read/es6-3rd/docs-generator.md" >《Generator 函数》<i class="fas fa-external-link-alt"></i></a>一章），原生具有 Iterator 接口。解构赋值会依次从这个接口获取值。</p>
<h3 id="默认值"><a href="#默认值" class="headerlink" title="默认值"></a>默认值</h3><p>解构赋值<strong>允许指定默认值</strong>。</p>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br></pre></td><td class="code"><pre><span class="line">let [foo = true] = [];</span><br><span class="line">foo // true</span><br><span class="line">let [x, y = &#x27;b&#x27;] = [&#x27;a&#x27;]; // x=&#x27;a&#x27;, y=&#x27;b&#x27;</span><br><span class="line">let [x, y = &#x27;b&#x27;] = [&#x27;a&#x27;, undefined]; // x=&#x27;a&#x27;, y=&#x27;b&#x27;</span><br></pre></td></tr></table></figure>

<blockquote>
<p><strong>注意，ES6 内部使用严格相等运算符（&#x3D;&#x3D;&#x3D;），判断一个位置是否有值。所以，只有当一个数组成员严格等于undefined，默认值才会生效</strong>。</p>
</blockquote>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br></pre></td><td class="code"><pre><span class="line">let [x = 1] = [undefined];</span><br><span class="line">x // 1</span><br><span class="line">let [x = 1] = [null];</span><br><span class="line">x // null</span><br></pre></td></tr></table></figure>

<p>上面代码中，如果一个数组成员是null，默认值就不会生效，因为null不严格等于undefined。</p>
<p>如果<strong>默认值是一个表达式，那么这个表达式是惰性求值的，即只有在用到的时候，才会求值</strong>。</p>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br></pre></td><td class="code"><pre><span class="line">function f() &#123;</span><br><span class="line">  console.log(&#x27;aaa&#x27;);</span><br><span class="line">&#125;</span><br><span class="line">let [x = f()] = [1];</span><br></pre></td></tr></table></figure>

<p>上面代码中，因为x能取到值，所以函数f根本不会执行。上面的代码其实等价于下面的代码。</p>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br></pre></td><td class="code"><pre><span class="line">let x;</span><br><span class="line">if ([1][0] === undefined) &#123;</span><br><span class="line">  x = f();</span><br><span class="line">&#125; else &#123;</span><br><span class="line">  x = [1][0];</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure>
<p><strong>默认值可以引用解构赋值的其他变量，但该变量必须已经声明</strong>。</p>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br></pre></td><td class="code"><pre><span class="line">let [x = 1, y = x] = [];     // x=1; y=1</span><br><span class="line">let [x = 1, y = x] = [2];    // x=2; y=2</span><br><span class="line">let [x = 1, y = x] = [1, 2]; // x=1; y=2</span><br><span class="line">let [x = y, y = 1] = [];     // ReferenceError: y is not defined</span><br></pre></td></tr></table></figure>
<p>上面最后一个表达式之所以会报错，是因为x用y做默认值时，y还没有声明。</p>
<hr>
<h1 id="2、对象的解构赋值"><a href="#2、对象的解构赋值" class="headerlink" title="2、对象的解构赋值"></a>2、对象的解构赋值</h1><h3 id="简介"><a href="#简介" class="headerlink" title="简介"></a>简介</h3><p>对象的解构与数组有一个重要的不同。<strong>数组的元素是按次序排列的，变量的取值由它的位置决定；而对象的属性没有次序，变量必须与属性同名，才能取到正确的值</strong>。</p>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br></pre></td><td class="code"><pre><span class="line">let &#123; bar, foo &#125; = &#123; foo: &#x27;aaa&#x27;, bar: &#x27;bbb&#x27; &#125;;</span><br><span class="line">foo // &quot;aaa&quot;</span><br><span class="line">bar // &quot;bbb&quot;</span><br><span class="line">let &#123; baz &#125; = &#123; foo: &#x27;aaa&#x27;, bar: &#x27;bbb&#x27; &#125;;</span><br><span class="line">baz // undefined</span><br></pre></td></tr></table></figure>

<p>上面代码的第一个例子，等号左边的两个变量的次序，与等号右边两个同名属性的次序不一致，但是对取值完全没有影响。第二个例子的变量没有对应的同名属性，导致取不到值，最后等于undefined。</p>
<p><strong>如果解构失败，变量的值等于undefined</strong>。</p>
<p>对象的解构赋值，可以很方便地将现有对象的方法，赋值到某个变量。</p>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br></pre></td><td class="code"><pre><span class="line">// 例一</span><br><span class="line">let &#123; log, sin, cos &#125; = Math;</span><br><span class="line">// 例二</span><br><span class="line">const &#123; log &#125; = console;</span><br><span class="line">log(&#x27;hello&#x27;) // hello</span><br></pre></td></tr></table></figure>
<p>上面代码的例一将Math对象的对数、正弦、余弦三个方法，赋值到对应的变量上，使用起来就会方便很多。例二将console.log赋值到log变量。</p>
<p>如果<strong>变量名与属性名不一致</strong>，必须写成下面这样。</p>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br></pre></td><td class="code"><pre><span class="line">let &#123; foo: baz &#125; = &#123; foo: &#x27;aaa&#x27;, bar: &#x27;bbb&#x27; &#125;;</span><br><span class="line">baz // &quot;aaa&quot;</span><br><span class="line">let obj = &#123; first: &#x27;hello&#x27;, last: &#x27;world&#x27; &#125;;</span><br><span class="line">let &#123; first: f, last: l &#125; = obj;</span><br><span class="line">f // &#x27;hello&#x27;</span><br><span class="line">l // &#x27;world&#x27;</span><br></pre></td></tr></table></figure>
<p>这实际上说明，对象的解构赋值是下面形式的简写（参见<a class="link"   target="_blank" rel="noopener" href="https://www.bookstack.cn/read/es6-3rd/docs-object.md" >《对象的扩展》<i class="fas fa-external-link-alt"></i></a>一章）。</p>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">let &#123; foo: foo, bar: bar &#125; = &#123; foo: &#x27;aaa&#x27;, bar: &#x27;bbb&#x27; &#125;;</span><br></pre></td></tr></table></figure>

<p>也就是说，<strong>对象的解构赋值的内部机制，是先找到同名属性，然后再赋给对应的变量</strong>。真正被赋值的是后者，而不是前者。</p>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line">let &#123; foo: baz &#125; = &#123; foo: &#x27;aaa&#x27;, bar: &#x27;bbb&#x27; &#125;;</span><br><span class="line">baz // &quot;aaa&quot;</span><br><span class="line">foo // error: foo is not defined</span><br></pre></td></tr></table></figure>

<p>上面代码中，foo是匹配的模式，baz才是变量。真正被赋值的是变量baz，而不是模式foo。</p>
<p>与数组一样，<strong>解构也可以用于嵌套结构的对象</strong>。</p>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br></pre></td><td class="code"><pre><span class="line">let obj = &#123;</span><br><span class="line">  p: [</span><br><span class="line">    &#x27;Hello&#x27;,</span><br><span class="line">    &#123; y: &#x27;World&#x27; &#125;</span><br><span class="line">  ]</span><br><span class="line">&#125;;</span><br><span class="line">let &#123; p: [x, &#123; y &#125;] &#125; = obj;</span><br><span class="line">x // &quot;Hello&quot;</span><br><span class="line">y // &quot;World&quot;</span><br></pre></td></tr></table></figure>
<p>注意，这时p是模式，不是变量，因此不会被赋值。如果p也要作为变量赋值，可以写成下面这样。</p>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br></pre></td><td class="code"><pre><span class="line">let obj = &#123;</span><br><span class="line">  p: [</span><br><span class="line">    &#x27;Hello&#x27;,</span><br><span class="line">    &#123; y: &#x27;World&#x27; &#125;</span><br><span class="line">  ]</span><br><span class="line">&#125;;</span><br><span class="line">let &#123; p, p: [x, &#123; y &#125;] &#125; = obj;</span><br><span class="line">x // &quot;Hello&quot;</span><br><span class="line">y // &quot;World&quot;</span><br><span class="line">p // [&quot;Hello&quot;, &#123;y: &quot;World&quot;&#125;]</span><br></pre></td></tr></table></figure>
<p>下面是另一个例子。</p>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br></pre></td><td class="code"><pre><span class="line">const node = &#123;</span><br><span class="line">  loc: &#123;</span><br><span class="line">    start: &#123;</span><br><span class="line">      line: 1,</span><br><span class="line">      column: 5</span><br><span class="line">    &#125;</span><br><span class="line">  &#125;</span><br><span class="line">&#125;;</span><br><span class="line">let &#123; loc, loc: &#123; start &#125;, loc: &#123; start: &#123; line &#125;&#125; &#125; = node;</span><br><span class="line">line // 1</span><br><span class="line">loc  // Object &#123;start: Object&#125;</span><br><span class="line">start // Object &#123;line: 1, column: 5&#125;</span><br></pre></td></tr></table></figure>
<p>上面代码有三次解构赋值，分别是对loc、start、line三个属性的解构赋值。注意，最后一次对line属性的解构赋值之中，只有line是变量，loc和start都是模式，不是变量。</p>
<p>下面是<strong>嵌套赋值</strong>的例子。</p>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br></pre></td><td class="code"><pre><span class="line">let obj = &#123;&#125;;</span><br><span class="line">let arr = [];</span><br><span class="line">(&#123; foo: obj.prop, bar: arr[0] &#125; = &#123; foo: 123, bar: true &#125;);</span><br><span class="line">obj // &#123;prop:123&#125;</span><br><span class="line">arr // [true]</span><br></pre></td></tr></table></figure>
<p>如果解构模式是嵌套的对象，而且子对象所在的父属性不存在，那么将会报错。</p>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line">// 报错</span><br><span class="line">let &#123;foo: &#123;bar&#125;&#125; = &#123;baz: &#x27;baz&#x27;&#125;;</span><br></pre></td></tr></table></figure>
<p>上面代码中，等号左边对象的foo属性，对应一个子对象。该子对象的bar属性，解构时会报错。原因很简单，因为foo这时等于undefined，再取子属性就会报错。</p>
<p>注意，<strong>对象的解构赋值可以取到继承的属性</strong>。</p>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br></pre></td><td class="code"><pre><span class="line">const obj1 = &#123;&#125;;</span><br><span class="line">const obj2 = &#123; foo: &#x27;bar&#x27; &#125;;</span><br><span class="line">Object.setPrototypeOf(obj1, obj2);</span><br><span class="line">const &#123; foo &#125; = obj1;</span><br><span class="line">foo // &quot;bar&quot;</span><br></pre></td></tr></table></figure>
<p>上面代码中，对象obj1的原型对象是obj2。foo属性不是obj1自身的属性，而是继承自obj2的属性，解构赋值可以取到这个属性。</p>
<h3 id="默认值-1"><a href="#默认值-1" class="headerlink" title="默认值"></a>默认值</h3><p>对象的解构也可以指定默认值。</p>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br></pre></td><td class="code"><pre><span class="line">var &#123;x = 3&#125; = &#123;&#125;;</span><br><span class="line">x // 3</span><br><span class="line">var &#123;x, y = 5&#125; = &#123;x: 1&#125;;</span><br><span class="line">x // 1</span><br><span class="line">y // 5</span><br><span class="line">var &#123;x: y = 3&#125; = &#123;&#125;;</span><br><span class="line">y // 3</span><br><span class="line">var &#123;x: y = 3&#125; = &#123;x: 5&#125;;</span><br><span class="line">y // 5</span><br><span class="line">var &#123; message: msg = &#x27;Something went wrong&#x27; &#125; = &#123;&#125;;</span><br><span class="line">msg // &quot;Something went wrong&quot;</span><br></pre></td></tr></table></figure>

<p><strong>默认值生效的条件是，对象的属性值严格等于undefined</strong>。</p>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br></pre></td><td class="code"><pre><span class="line">var &#123;x = 3&#125; = &#123;x: undefined&#125;;</span><br><span class="line">x // 3</span><br><span class="line">var &#123;x = 3&#125; = &#123;x: null&#125;;</span><br><span class="line">x // null</span><br></pre></td></tr></table></figure>

<p>上面代码中，属性x等于null，因为null与undefined不严格相等，所以是个有效的赋值，导致默认值3不会生效。</p>
<h3 id="注意点"><a href="#注意点" class="headerlink" title="注意点"></a>注意点</h3><p>（1）如果要将一个已经声明的变量用于解构赋值，必须非常小心。</p>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br></pre></td><td class="code"><pre><span class="line">// 错误的写法</span><br><span class="line">let x;</span><br><span class="line">&#123;x&#125; = &#123;x: 1&#125;;</span><br><span class="line">// SyntaxError: syntax error</span><br></pre></td></tr></table></figure>

<p>上面代码的写法会报错，因为 JavaScript 引擎会将{x}理解成一个代码块，从而发生语法错误。只有不将大括号写在行首，避免 JavaScript 将其解释为代码块，才能解决这个问题。</p>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line">// 正确的写法</span><br><span class="line">let x;</span><br><span class="line">(&#123;x&#125; = &#123;x: 1&#125;);</span><br></pre></td></tr></table></figure>

<p>上面代码将整个解构赋值语句，放在一个圆括号里面，就可以正确执行。关于圆括号与解构赋值的关系，参见下文。</p>
<p>（2）解构赋值允许等号左边的模式之中，不放置任何变量名。因此，可以写出非常古怪的赋值表达式。</p>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line">(&#123;&#125; = [true, false]);</span><br><span class="line">(&#123;&#125; = &#x27;abc&#x27;);</span><br><span class="line">(&#123;&#125; = []);</span><br></pre></td></tr></table></figure>

<p>上面的表达式虽然毫无意义，但是语法是合法的，可以执行。</p>
<p>（3）由于数组本质是特殊的对象，因此可以对数组进行对象属性的解构。</p>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br></pre></td><td class="code"><pre><span class="line">let arr = [1, 2, 3];</span><br><span class="line">let &#123;0 : first, [arr.length - 1] : last&#125; = arr;</span><br><span class="line">first // 1</span><br><span class="line">last // 3</span><br></pre></td></tr></table></figure>

<p>上面代码对数组进行对象解构。数组arr的0键对应的值是1，[arr.length - 1]就是2键，对应的值是3。方括号这种写法，属于“属性名表达式”（参见<a class="link"   target="_blank" rel="noopener" href="https://www.bookstack.cn/read/es6-3rd/docs-object.md" >《对象的扩展》<i class="fas fa-external-link-alt"></i></a>一章）。</p>
<hr>
<h1 id="3、字符串的解构赋值"><a href="#3、字符串的解构赋值" class="headerlink" title="3、字符串的解构赋值"></a>3、字符串的解构赋值</h1><p>字符串也可以解构赋值。这是因为此时，<strong>字符串被转换成了一个类似数组的对象</strong>。</p>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br></pre></td><td class="code"><pre><span class="line">const [a, b, c, d, e] = &#x27;hello&#x27;;</span><br><span class="line">a // &quot;h&quot;</span><br><span class="line">b // &quot;e&quot;</span><br><span class="line">c // &quot;l&quot;</span><br><span class="line">d // &quot;l&quot;</span><br><span class="line">e // &quot;o&quot;</span><br></pre></td></tr></table></figure>

<p>类似数组的对象都有一个length属性，因此还可以对这个属性解构赋值。</p>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line">let &#123;length : len&#125; = &#x27;hello&#x27;;</span><br><span class="line">len // 5</span><br></pre></td></tr></table></figure>

<hr>
<h1 id="4、数值和布尔值的解构赋值"><a href="#4、数值和布尔值的解构赋值" class="headerlink" title="4、数值和布尔值的解构赋值"></a>4、数值和布尔值的解构赋值</h1><p>解构赋值时，如果等号右边是数值和布尔值，则会先转为对象。</p>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br></pre></td><td class="code"><pre><span class="line">let &#123;toString: s&#125; = 123;</span><br><span class="line">s === Number.prototype.toString     // true</span><br><span class="line">let &#123;toString: s&#125; = true;           //相当于123这个Number的方法toString 赋值给s</span><br><span class="line">s === Boolean.prototype.toString    // true</span><br><span class="line">s.call(111)                         //&#x27;111&#x27;</span><br></pre></td></tr></table></figure>

<p>上面代码中，数值和布尔值的包装对象都有toString属性，因此变量s都能取到值。</p>
<blockquote>
<p><strong>如果等号右边是数值或者布尔值，那么会先转为对象</strong>，指的是等号右边的数值或者布尔值转换为对象，而这个对象里面包含一个toString方法。对象里定义方法一般是按照这种形式：<br>var obj &#x3D; {<br>    toString:function(){}<br>}<br>所以通过let{toString：s}&#x3D;123，此时123转换为了一个对象，对象的解构赋值需要查找相同属性名，所以当在123这个对象中找到相同的属性名也就是toString时那么s就会被赋值toString的属性值也就是一个function（）。</p>
</blockquote>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line">s           //ƒ toString() &#123; [native code] &#125;</span><br><span class="line">s.call(21)  //&#x27;21&#x27;</span><br></pre></td></tr></table></figure>


<p>解构赋值的规则是，只要等号右边的值不是对象或数组，就先将其转为对象。<strong>由于undefined和null无法转为对象，所以对它们进行解构赋值，都会报错</strong>。</p>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line">let &#123; prop: x &#125; = undefined; // TypeError</span><br><span class="line">let &#123; prop: y &#125; = null; // TypeError</span><br></pre></td></tr></table></figure>

<hr>
<h1 id="5、函数参数的解构赋值"><a href="#5、函数参数的解构赋值" class="headerlink" title="5、函数参数的解构赋值"></a>5、函数参数的解构赋值</h1><p>函数的参数也可以使用解构赋值。</p>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br></pre></td><td class="code"><pre><span class="line">function add([x, y])&#123;</span><br><span class="line">  return x + y;</span><br><span class="line">&#125;</span><br><span class="line">add([1, 2]); // 3</span><br></pre></td></tr></table></figure>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line">[[1, 2], [3, 4]].map(([a, b]) =&gt; a + b);</span><br><span class="line">// [ 3, 7 ]</span><br></pre></td></tr></table></figure>

<p>上面代码中，函数add的参数表面上是一个数组，但在传入参数的那一刻，数组参数就被解构成变量x和y。<strong>对于函数内部的代码来说，它们能感受到的参数就是x和y</strong>。</p>
<p><strong>函数参数的解构也可以使用默认值</strong>。</p>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br></pre></td><td class="code"><pre><span class="line">function move(&#123;x = 0, y = 0&#125; = &#123;&#125;) &#123;</span><br><span class="line">  return [x, y];</span><br><span class="line">&#125;</span><br><span class="line">move(&#123;x: 3, y: 8&#125;); // [3, 8]</span><br><span class="line">move(&#123;x: 3&#125;); // [3, 0]</span><br><span class="line">move(&#123;&#125;); // [0, 0]</span><br><span class="line">move(); // [0, 0]</span><br></pre></td></tr></table></figure>

<p>上面代码中，函数move的参数是一个对象，通过对这个对象进行解构，得到变量x和y的值。<strong>如果解构失败，x和y等于默认值</strong>。</p>
<p>注意，下面的写法会得到不一样的结果。</p>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br></pre></td><td class="code"><pre><span class="line">function move(&#123;x, y&#125; = &#123; x: 0, y: 0 &#125;) &#123;</span><br><span class="line">  return [x, y];</span><br><span class="line">&#125;</span><br><span class="line">move(&#123;x: 3, y: 8&#125;); // [3, 8]</span><br><span class="line">move(&#123;x: 3&#125;); // [3, undefined]</span><br><span class="line">move(&#123;&#125;); // [undefined, undefined]</span><br><span class="line">move(); // [0, 0]</span><br></pre></td></tr></table></figure>

<p>上面代码是为函数move的参数指定默认值，而不是为变量x和y指定默认值，所以会得到与前一种写法不同的结果。</p>
<p><strong>undefined就会触发函数参数的默认值</strong>。</p>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line">[1, undefined, 3].map((x = &#x27;yes&#x27;) =&gt; x);</span><br><span class="line">// [ 1, &#x27;yes&#x27;, 3 ]</span><br></pre></td></tr></table></figure>

<hr>
<h1 id="6、圆括号问题"><a href="#6、圆括号问题" class="headerlink" title="6、圆括号问题"></a>6、圆括号问题</h1><p>解构赋值虽然很方便，但是解析起来并不容易。对于编译器来说，一个式子到底是模式，还是表达式，没有办法从一开始就知道，必须解析到（或解析不到）等号才能知道。</p>
<p>由此带来的问题是，如果模式中出现圆括号怎么处理。ES6 的规则是，<strong>只要有可能导致解构的歧义，就不得使用圆括号</strong>。</p>
<p>但是，这条规则实际上不那么容易辨别，处理起来相当麻烦。因此，建议<strong>只要有可能，就不要在模式中放置圆括号</strong>。</p>
<h3 id="不能使用圆括号的情况"><a href="#不能使用圆括号的情况" class="headerlink" title="不能使用圆括号的情况"></a>不能使用圆括号的情况</h3><p>以下三种解构赋值不得使用圆括号。</p>
<p>（1）变量声明语句</p>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br></pre></td><td class="code"><pre><span class="line">// 全部报错</span><br><span class="line">let [(a)] = [1];</span><br><span class="line">let &#123;x: (c)&#125; = &#123;&#125;;</span><br><span class="line">let (&#123;x: c&#125;) = &#123;&#125;;</span><br><span class="line">let &#123;(x: c)&#125; = &#123;&#125;;</span><br><span class="line">let &#123;(x): c&#125; = &#123;&#125;;</span><br><span class="line">let &#123; o: (&#123; p: p &#125;) &#125; = &#123; o: &#123; p: 2 &#125; &#125;;</span><br></pre></td></tr></table></figure>

<p>上面 6 个语句都会报错，因为它们都是变量声明语句，模式不能使用圆括号。</p>
<p>（2）函数参数</p>
<p>函数参数也属于变量声明，因此不能带有圆括号。</p>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br></pre></td><td class="code"><pre><span class="line">// 报错</span><br><span class="line">function f([(z)]) &#123; return z; &#125;</span><br><span class="line">// 报错</span><br><span class="line">function f([z,(x)]) &#123; return x; &#125;</span><br></pre></td></tr></table></figure>

<p>（3）赋值语句的模式</p>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line">// 全部报错</span><br><span class="line">(&#123; p: a &#125;) = &#123; p: 42 &#125;;</span><br><span class="line">([a]) = [5];</span><br></pre></td></tr></table></figure>

<p>上面代码将整个模式放在圆括号之中，导致报错。</p>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line">// 报错</span><br><span class="line">[(&#123; p: a &#125;), &#123; x: c &#125;] = [&#123;&#125;, &#123;&#125;];</span><br></pre></td></tr></table></figure>

<p>上面代码将一部分模式放在圆括号之中，导致报错。</p>
<h3 id="可以使用圆括号的情况"><a href="#可以使用圆括号的情况" class="headerlink" title="可以使用圆括号的情况"></a>可以使用圆括号的情况</h3><p>可以使用圆括号的情况<strong>只有一种：赋值语句的非模式部分，可以使用圆括号</strong>。</p>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line">[(b)] = [3]; // 正确</span><br><span class="line">(&#123; p: (d) &#125; = &#123;&#125;); // 正确</span><br><span class="line">[(parseInt.prop)] = [3]; // 正确</span><br></pre></td></tr></table></figure>

<p>上面三行语句都可以正确执行，因为首先它们都是赋值语句，而不是声明语句；其次它们的圆括号都不属于模式的一部分。第一行语句中，模式是取数组的第一个成员，跟圆括号无关；第二行语句中，模式是p，而不是d；第三行语句与第一行语句的性质一致。</p>
<hr>
<h1 id="7、用途"><a href="#7、用途" class="headerlink" title="7、用途"></a>7、用途</h1><p>变量的解构赋值用途很多。</p>
<h4 id="（1）交换变量的值"><a href="#（1）交换变量的值" class="headerlink" title="（1）交换变量的值"></a>（1）交换变量的值</h4><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line">let x = 1;</span><br><span class="line">let y = 2;</span><br><span class="line">[x, y] = [y, x];</span><br></pre></td></tr></table></figure>

<p>上面代码交换变量x和y的值，这样的写法不仅简洁，而且易读，语义非常清晰。</p>
<h4 id="（2）从函数返回多个值"><a href="#（2）从函数返回多个值" class="headerlink" title="（2）从函数返回多个值"></a>（2）从函数返回多个值</h4><p>函数只能返回一个值，如果要返回多个值，只能将它们放在数组或对象里返回。有了解构赋值，取出这些值就非常方便。</p>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br></pre></td><td class="code"><pre><span class="line">// 返回一个数组</span><br><span class="line">function example() &#123;</span><br><span class="line">  return [1, 2, 3];</span><br><span class="line">&#125;</span><br><span class="line">let [a, b, c] = example();</span><br><span class="line">// 返回一个对象</span><br><span class="line">function example() &#123;</span><br><span class="line">  return &#123;</span><br><span class="line">    foo: 1,</span><br><span class="line">    bar: 2</span><br><span class="line">  &#125;;</span><br><span class="line">&#125;</span><br><span class="line">let &#123; foo, bar &#125; = example();</span><br></pre></td></tr></table></figure>

<h4 id="（3）函数参数的定义"><a href="#（3）函数参数的定义" class="headerlink" title="（3）函数参数的定义"></a>（3）函数参数的定义</h4><p>解构赋值可以方便地将一组参数与变量名对应起来。</p>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br></pre></td><td class="code"><pre><span class="line">// 参数是一组有次序的值</span><br><span class="line">function f([x, y, z]) &#123; ... &#125;</span><br><span class="line">f([1, 2, 3]);</span><br><span class="line">// 参数是一组无次序的值</span><br><span class="line">function f(&#123;x, y, z&#125;) &#123; ... &#125;</span><br><span class="line">f(&#123;z: 3, y: 2, x: 1&#125;);</span><br></pre></td></tr></table></figure>

<h4 id="（4）提取-JSON-数据"><a href="#（4）提取-JSON-数据" class="headerlink" title="（4）提取 JSON 数据"></a>（4）提取 JSON 数据</h4><p>解构赋值对提取 JSON 对象中的数据，尤其有用。</p>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br></pre></td><td class="code"><pre><span class="line">let jsonData = &#123;</span><br><span class="line">  id: 42,</span><br><span class="line">  status: &quot;OK&quot;,</span><br><span class="line">  data: [867, 5309]</span><br><span class="line">&#125;;</span><br><span class="line">let &#123; id, status, data: number &#125; = jsonData;</span><br><span class="line">console.log(id, status, number);</span><br><span class="line">// 42, &quot;OK&quot;, [867, 5309]</span><br></pre></td></tr></table></figure>

<p>上面代码可以快速提取 JSON 数据的值。</p>
<h4 id="（5）函数参数的默认值"><a href="#（5）函数参数的默认值" class="headerlink" title="（5）函数参数的默认值"></a>（5）函数参数的默认值</h4><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br></pre></td><td class="code"><pre><span class="line">jQuery.ajax = function (url, &#123;</span><br><span class="line">  async = true,</span><br><span class="line">  beforeSend = function () &#123;&#125;,</span><br><span class="line">  cache = true,</span><br><span class="line">  complete = function () &#123;&#125;,</span><br><span class="line">  crossDomain = false,</span><br><span class="line">  global = true,</span><br><span class="line">  // ... more config</span><br><span class="line">&#125; = &#123;&#125;) &#123;</span><br><span class="line">  // ... do stuff</span><br><span class="line">&#125;;</span><br></pre></td></tr></table></figure>

<p>指定参数的默认值，就避免了在函数体内部再写var foo &#x3D; config.foo || ‘default foo’;这样的语句。</p>
<h4 id="（6）遍历-Map-结构"><a href="#（6）遍历-Map-结构" class="headerlink" title="（6）遍历 Map 结构"></a>（6）遍历 Map 结构</h4><p>任何部署了 Iterator 接口的对象，都可以用for…of循环遍历。Map 结构原生支持 Iterator 接口，配合变量的解构赋值，获取键名和键值就非常方便。</p>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br></pre></td><td class="code"><pre><span class="line">const map = new Map();</span><br><span class="line">map.set(&#x27;first&#x27;, &#x27;hello&#x27;);</span><br><span class="line">map.set(&#x27;second&#x27;, &#x27;world&#x27;);</span><br><span class="line">for (let [key, value] of map) &#123;</span><br><span class="line">  console.log(key + &quot; is &quot; + value);</span><br><span class="line">&#125;</span><br><span class="line">// first is hello</span><br><span class="line">// second is world</span><br><span class="line">如果只想获取键名，或者只想获取键值，可以写成下面这样。</span><br><span class="line"></span><br><span class="line">// 获取键名</span><br><span class="line">for (let [key] of map) &#123;</span><br><span class="line">  // ...</span><br><span class="line">&#125;</span><br><span class="line">// 获取键值</span><br><span class="line">for (let [,value] of map) &#123;</span><br><span class="line">  // ...</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure>

<h4 id="（7）输入模块的指定方法"><a href="#（7）输入模块的指定方法" class="headerlink" title="（7）输入模块的指定方法"></a>（7）输入模块的指定方法</h4><p>加载模块时，往往需要指定输入哪些方法。解构赋值使得输入语句非常清晰。</p>
<figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">const &#123; SourceMapConsumer, SourceNode &#125; = require(&quot;source-map&quot;);</span><br></pre></td></tr></table></figure>

<hr>
<p><em><strong>参考文献</strong></em></p>
<p><a class="link"   target="_blank" rel="noopener" href="https://www.bookstack.cn/read/es6-3rd/docs-destructuring.md" >阮一峰 ECMAScript 6 (ES6) 标准入门教程 第三版<i class="fas fa-external-link-alt"></i></a></p>
<p><a class="link"   target="_blank" rel="noopener" href="https://blog.csdn.net/weixin_39370093/article/details/121146672" >【JS】解构在函数中的使用<i class="fas fa-external-link-alt"></i></a></p>
<p><a class="link"   target="_blank" rel="noopener" href="https://segmentfault.com/q/1010000005647566" >数值和布尔值的解构赋值的一个问题<i class="fas fa-external-link-alt"></i></a></p>

            </div>

            

            
                <ul class="post-tags-box">
                    
                        <li class="tag-item">
                            <a href="/tags/%E8%A7%A3%E6%9E%84/">#解构</a>&nbsp;
                        </li>
                    
                        <li class="tag-item">
                            <a href="/tags/ES6/">#ES6</a>&nbsp;
                        </li>
                    
                </ul>
            

            
                <div class="article-nav">
                    
                        <div class="article-prev">
                            <a class="prev"
                               rel="prev"
                               href="/2023/06/06/JavaScript%E4%B9%8B%E5%AD%97%E7%AC%A6%E4%B8%B2%E6%93%8D%E4%BD%9C/"
                            >
                            <span class="left arrow-icon flex-center">
                              <i class="fas fa-chevron-left"></i>
                            </span>
                                <span class="title flex-center">
                                <span class="post-nav-title-item">Javascript之字符串操作</span>
                                <span class="post-nav-item">Prev posts</span>
                            </span>
                            </a>
                        </div>
                    
                    
                        <div class="article-next">
                            <a class="next"
                               rel="next"
                               href="/2023/06/05/Vue%E4%B9%8Bv-if%E4%B8%8Ev-show/"
                            >
                            <span class="title flex-center">
                                <span class="post-nav-title-item">Vue之v-if与v-show</span>
                                <span class="post-nav-item">Next posts</span>
                            </span>
                                <span class="right arrow-icon flex-center">
                              <i class="fas fa-chevron-right"></i>
                            </span>
                            </a>
                        </div>
                    
                </div>
            

            
        </div>

        
    </div>
</div>


                
            </div>

        </div>

        <div class="page-main-content-bottom">
            
<footer class="footer">
    <div class="info-container">
        <div class="copyright-info info-item">
            &copy;
            
                <span>2020</span> -
            
            2024
            
                &nbsp;<i class="fas fa-heart icon-animate"></i>
                &nbsp;<a href="/">aaton</a>
            
        </div>
        
            <script async 
                    src="//busuanzi.ibruce.info/busuanzi/2.3/busuanzi.pure.mini.js"></script>
            <div class="website-count info-item">
                
                    Visitor Count&nbsp;<span id="busuanzi_value_site_uv"></span>&ensp;
                
                
                    Totalview&nbsp;<span id="busuanzi_value_site_pv"></span>
                
            </div>
        
        <div class="theme-info info-item">
            Powered by <a target="_blank" href="https://hexo.io">Hexo</a>&nbsp;|&nbsp;Theme&nbsp;<a class="theme-version" target="_blank" href="https://github.com/XPoet/hexo-theme-keep">Keep v3.6.1</a>
        </div>
        
        
    </div>
</footer>

        </div>
    </div>

    
        <div class="post-tools">
            <div class="post-tools-container">
    <ul class="tools-list">
        <!-- TOC aside toggle -->
        

        <!-- go comment -->
        
    </ul>
</div>

        </div>
    

    <div class="right-bottom-side-tools">
        <div class="side-tools-container">
    <ul class="side-tools-list">
        <li class="tools-item tool-font-adjust-plus flex-center">
            <i class="fas fa-search-plus"></i>
        </li>

        <li class="tools-item tool-font-adjust-minus flex-center">
            <i class="fas fa-search-minus"></i>
        </li>

        <li class="tools-item tool-dark-light-toggle flex-center">
            <i class="fas fa-moon"></i>
        </li>

        <!-- rss -->
        

        
            <li class="tools-item tool-scroll-to-top flex-center">
                <i class="fas fa-arrow-up"></i>
            </li>
        

        <li class="tools-item tool-scroll-to-bottom flex-center">
            <i class="fas fa-arrow-down"></i>
        </li>
    </ul>

    <ul class="exposed-tools-list">
        <li class="tools-item tool-toggle-show flex-center">
            <i class="fas fa-cog fa-spin"></i>
        </li>
        
    </ul>
</div>

    </div>

    <div class="zoom-in-image-mask">
    <img class="zoom-in-image">
</div>


    

</main>




<script src="/js/utils.js"></script>

<script src="/js/main.js"></script>

<script src="/js/header-shrink.js"></script>

<script src="/js/back2top.js"></script>

<script src="/js/dark-light-toggle.js"></script>







    
<script src="/js/code-block.js"></script>





<div class="post-scripts">
    
        
<script src="/js/post-helper.js"></script>

        
        
    
</div>



</body>
</html>
